package org.zn.note.designpattern;

/**
 * 桥接模式（Bridge）
 * 用于把抽象化与实现化解耦，使得二者可以独立变化。
 * 这种模式涉及到一个作为桥接的接口，使得实体类的功能独立于接口实现类。这两种类型的类可被结构化改变而互不影响。
 * <p>
 * 本来的逻辑：图（接口 draw） --> 圆（实现 DrawAPI.drawCircle） --> 不同颜色的圆 （依然是圆实例，但是功能通过DrawAPI的不同实例实现）
 * <p>
 * 有两层抽象：一层是对实体类(图 --> 圆)抽象、一层是对实体类的某个功能抽象(画圆 --> 画不同颜色的圆)
 * <p>
 * 理解起来有点费劲，增加系统复杂度
 * <p>
 * 还是上面的例子，比如图形有 圆、三角形、正方形，然后颜色有 红色、黄色、绿色
 * 方案一：不同颜色的图形，两两组合，有 9 个实现类。而且每个实现类的图形和颜色功能代码偶尔在一起。
 * 方案二：将颜色单独拿出来，通过组合的形式，放到图形中。也就是创建图形的时候，传入颜色实现类。
 */
public class Pattern07_Bridge {

    public static void main(String[] args) {
        Shape redCircle = new Circle(100, 100, 10, new RedCircle());
        Shape greenCircle = new Circle(100, 100, 10, new GreenCircle());

        redCircle.draw();
        greenCircle.draw();
    }

    // 画圆
    private interface DrawAPI {
        void drawCircle(int radius, int x, int y);
    }

    private static abstract class Shape {
        DrawAPI drawAPI;

        Shape(DrawAPI drawAPI) {
            this.drawAPI = drawAPI;
        }

        public abstract void draw();
    }

    private static class Circle extends Shape {
        private int x, y, radius;

        public Circle(int x, int y, int radius, DrawAPI drawAPI) {
            super(drawAPI);
            this.x = x;
            this.y = y;
            this.radius = radius;
        }

        public void draw() {
            drawAPI.drawCircle(radius, x, y);
        }
    }

    // 红色的圆
    private static class RedCircle implements DrawAPI {
        @Override
        public void drawCircle(int radius, int x, int y) {
            System.out.println("Drawing Circle[ color: red, radius: "
                    + radius + ", x: " + x + ", " + y + "]");
        }
    }

    // 绿色的圆
    private static class GreenCircle implements DrawAPI {
        @Override
        public void drawCircle(int radius, int x, int y) {
            System.out.println("Drawing Circle[ color: green, radius: "
                    + radius + ", x: " + x + ", " + y + "]");
        }
    }
}
